home *** CD-ROM | disk | FTP | other *** search
/ Celestin Apprentice 7 / Apprentice-Release7.iso / Environments / Small Eiffel 0.4.8 / lib_std / general.e < prev    next >
Text File  |  1997-04-13  |  17KB  |  676 lines

  1. -- Part of SmallEiffel -- Read DISCLAIMER file -- Copyright (C) 
  2. -- Dominique COLNET and Suzanne COLLIN -- colnet@loria.fr
  3. --
  4. class GENERAL
  5. --        
  6. -- Platform-independent universal properties.
  7. -- This class is an ancestor to all developer-written classes.
  8. --
  9.  
  10. feature -- Access :
  11.    
  12.    generating_type: STRING is
  13.      -- Name of current object's generating type (type of 
  14.      -- which it is a direct instance).
  15.       external "CSE"
  16.       end;
  17.   
  18.    generator: STRING is
  19.      -- Name of current object's generating class (base class
  20.      -- of the type of witch it is a direct instance).
  21.       external "CSE"
  22.       end;
  23.    
  24.    id_object(id: INTEGER): ANY is
  25.      -- Object for wich `object_id' has returned `id'.
  26.      -- Void if none.
  27.       require
  28.      id /= 0;
  29.       do
  30.      Result := object_id_memory.item(id);
  31.       end;
  32.    
  33.    object_id: INTEGER is
  34.      -- Value identifying current reference object.
  35.       require
  36.      not is_expanded_type
  37.       do
  38.      Result := object_id_memory.fast_index_of(Current);
  39.      if Result > object_id_memory.upper then
  40.         object_id_memory.add_last(Current);
  41.      end;
  42.       end;
  43.    
  44.    stripped(other: GENERAL): like other is
  45.      -- New created object with fields copied from current object, but
  46.      -- limited to attributes of type of `other'.
  47.       require
  48.      conformance: conforms_to(other);
  49.       do
  50.      not_yet_implemented;
  51.       ensure
  52.      stripped_to_other: Result.same_type(other);
  53.       end;
  54.    
  55. feature -- Status report :
  56.    
  57.    frozen conforms_to(other: GENERAL): BOOLEAN is
  58.      -- Does type of current object conform to type of other 
  59.      -- (as per Eiffel: The Language, chapter 13) ?
  60.       require
  61.      other_not_void: other /= Void;
  62.      not is_expanded_type;
  63.          not other.is_expanded_type
  64.       local
  65.      x: like Current;
  66.       do
  67.      x ?= other;
  68.      Result := x /= Void;
  69.       end;
  70.    
  71.    frozen same_type(other: GENERAL): BOOLEAN is
  72.      -- Is type of current object identical to type of other.     
  73.       require
  74.      other_not_void: other /= Void;
  75.       do
  76.      if not is_expanded_type then
  77.         c_inline_c("R=((C->id)==(a1->id));");
  78.      end;
  79.       ensure
  80. --     definition: Result = (conforms_to(other) and
  81. --                   other.conforms_to(Current));
  82.       end;
  83.    
  84. feature -- Comparison :
  85.    
  86.    frozen deep_equal(some: GENERAL; other: like some): BOOLEAN is
  87.       do
  88.      if some = other then
  89.         Result := true;
  90.      elseif some = Void then
  91.      elseif other = Void then
  92.      elseif standard_equal(some,other) then
  93.         Result := true;
  94.      else
  95.         not_yet_implemented;
  96.      end;
  97.       ensure
  98.      shallow_implies_deep: standard_equal(some,other) 
  99.                    implies Result;
  100.      same_type: Result implies some.same_type(other);
  101.      symmetric: Result implies deep_equal(other,some);
  102.       end;
  103.    
  104.    frozen equal(some: ANY; other: like some): BOOLEAN is
  105.      -- Are `some' and `other' both Void or attached to
  106.      -- objects considered equal ?
  107.       do
  108.      if some = other then
  109.         Result := true;
  110.      elseif some = Void then
  111.      elseif other = Void then
  112.      else
  113.         Result := some.is_equal(other);
  114.      end;
  115.       ensure
  116.      definition: Result = (some = Void and other = Void) or else
  117.              ((some /= Void and other /= Void) and then
  118.               some.is_equal(other));
  119.       end;
  120.  
  121.    is_equal(other: like Current): BOOLEAN is
  122.      -- Is `other' attached to an object considered equal to 
  123.      -- current object ?
  124.       require
  125.      other_not_void: other /= Void
  126.       do
  127.      Result := standard_is_equal(other);
  128.       ensure
  129.      consistent: standard_is_equal(other) implies Result;
  130.      symmetric: Result implies other.is_equal(Current);
  131.       end;
  132.    
  133.    frozen standard_equal(some: ANY; other: like some): BOOLEAN is
  134.      -- Are `some' and `other' both Void or attached to
  135.      -- field-by-field objects of the same type ?
  136.      -- Always use the default object comparison criterion.
  137.       do
  138.      if some = other then
  139.         Result := true;
  140.      elseif some = Void then
  141.      elseif other = Void then
  142.      elseif some.same_type(other) then
  143.         Result := some.standard_is_equal(other);
  144.      end;
  145.       ensure
  146.      definition: Result = (some = Void and other = Void) or else
  147.              ((some /= Void and other /= Void) and then
  148.               some.standard_is_equal(other));
  149.       end;
  150.  
  151.    frozen standard_is_equal(other: like Current): BOOLEAN is
  152.      -- Are Current and `other' field-by-field identical?
  153.       require
  154.      other /= Void
  155.       do
  156.      if is_expanded_type then
  157.         Result := other = Current;
  158.      else
  159.         se_guru02;
  160.      end;
  161.       ensure
  162.      symmetric: Result implies other.standard_is_equal(Current);
  163.       end;
  164.    
  165. feature -- Duplication :
  166.    
  167.    frozen clone(other: ANY): like other is
  168.      -- When argument `other' is Void, return Void
  169.      -- otherwise return `other.twin'.
  170.       do
  171.      if other /= Void then
  172.         Result := other.twin;
  173.      end;
  174.       ensure
  175.      equal: equal(Result,other);
  176.       end;
  177.  
  178.    frozen twin: like Current is
  179.      -- Return an initialized new object using target as model.
  180.      -- Result as the same `generating_type' as the target of the 
  181.      -- call. Before to be returned, the corresponding `copy' feature
  182.      -- is called.
  183.       do
  184.      if is_expanded_type then
  185.         if is_basic_expanded_type then
  186.            Result := Current;
  187.         else
  188.            Result := Current;
  189.            Result.copy(Current);
  190.         end;
  191.      else
  192.         se_guru01;
  193.      end;
  194.       ensure
  195.      equal: Result.is_equal(Current);
  196.       end;
  197.  
  198.    copy(other: like Current) is
  199.      -- Update current object using fields of object attached
  200.      -- to `other', so as to yield equal objects.
  201.       require
  202.      other_not_void: other /= Void;
  203.      type_identity: same_type(other);
  204.       do
  205.      se_guru03;
  206.       ensure
  207.      is_equal: is_equal(other)
  208.       end;
  209.    
  210.    frozen deep_clone(other: GENERAL): like other is
  211.      -- Void if `other' is Void: otherwise, new object structure 
  212.      -- recursively duplicated from the one attached to other.
  213.       do
  214.      not_yet_implemented;
  215.       ensure
  216.      deep_equal: deep_equal(other,Result);
  217.       end;
  218.    
  219.    frozen standard_clone(other: ANY): like other is
  220.      -- Void if `other' is Void; otherwise new object 
  221.      -- field-by-field identical to `other'. 
  222.      -- Always use the default copying semantics.
  223.       do
  224.      if other /= Void then
  225.         Result := other.standard_twin;
  226.      end;
  227.       ensure
  228.      equal: standard_equal(Result,other);
  229.       end;
  230.  
  231.    frozen standard_twin: like Current is
  232.       do
  233.  
  234.      if is_expanded_type then
  235.         Result := Current;
  236.      else
  237.         c_inline_c("R=malloc(sizeof(*C));%N%
  238.                %memcpy(R,C,sizeof(*C));");
  239.      end;
  240.       end;
  241.       
  242.     frozen standard_copy(other: like Current) is
  243.      -- Copy every field of `other' onto corresponding 
  244.      -- field of curent object.
  245.       require
  246.      other_not_void: other /= Void;
  247.      type_identity: same_type(other);
  248.       do
  249.      c_inline_c("memcpy(C,a1,sizeof(*C));");
  250.       ensure
  251.      is_standard_equal: standard_is_equal(other);
  252.       end;
  253.    
  254. feature -- Basic operations :
  255.    
  256.    frozen default: like Current is
  257.      -- Default value of current type.
  258.       do
  259.       end;
  260.    
  261.    frozen default_pointer: POINTER is
  262.      -- Default value of type POINTER (avoid the need to
  263.       -- write p.default for some `p' of type POINTER).
  264.       do
  265.       ensure
  266.      Result = Result.default;
  267.       end;
  268.    
  269.    default_rescue is
  270.      -- Handle exception if no Rescue clause (default do
  271.      -- nothing).
  272.       do
  273.       end;
  274.    
  275.    frozen do_nothing is
  276.      -- Execute a null action.
  277.       do
  278.       end;
  279.    
  280.    frozen Void: NONE is 
  281.       -- Void reference.
  282.       external "CSE" 
  283.       end;
  284.  
  285. feature -- Input and Output :
  286.    
  287.    frozen io: STD_INPUT_OUTPUT is
  288.      -- Handle to standard file setup.
  289.      -- To use the standard input/output file.
  290.       once
  291.      !!Result.make;
  292.       ensure
  293.      Result /= Void;
  294.       end; 
  295.    
  296.    frozen std_input: STD_INPUT is
  297.      -- To use the standard input file.
  298.       once
  299.      !!Result.make;
  300.       end; 
  301.    
  302.    frozen std_output: STD_OUTPUT is
  303.      -- To use the standard output file.
  304.       once
  305.      !!Result.make;
  306.       end; 
  307.    
  308.    frozen std_error: STD_ERROR is
  309.      -- To use the standard error file.
  310.       once
  311.      !!Result.make;
  312.       end; 
  313.    
  314. feature -- Object Printing :
  315.  
  316.    print(some: GENERAL) is
  317.      -- Write terse external representation of `some' on
  318.      -- `standard_output'.
  319.      -- This routine is automatically called to print the stack
  320.      -- when system `crash'. As user can redefine `print', 
  321.      -- `print_on' or `fill_tagged_out_memory', it is better to 
  322.      --  be sure not to have a second `crash'. 
  323.       do
  324.      if some = Void then
  325.         std_output.put_string("Void");
  326.      else
  327.         some.print_on(std_output);
  328.      end;
  329.       end;
  330.    
  331.    print_on(file: STD_FILE_WRITE) is
  332.      -- Default printing of current object.
  333.       do
  334.      tagged_out_memory.clear;
  335.      out_in_tagged_out_memory;
  336.      file.put_string(tagged_out_memory);
  337.       end;
  338.  
  339.    frozen tagged_out: STRING is
  340.      -- New string containing printable representation of current 
  341.      -- object, each field preceded by its attribute name, a 
  342.      -- colon and a space.
  343.       do
  344.      tagged_out_memory.clear;
  345.      fill_tagged_out_memory;
  346.      Result := tagged_out_memory.twin;
  347.       end;
  348.    
  349.    out: STRING is
  350.      -- Create a new string containing terse printable 
  351.      -- representation of current object;
  352.       do
  353.      tagged_out_memory.clear;
  354.      out_in_tagged_out_memory;
  355.      Result := tagged_out_memory.twin;
  356.       end;
  357.    
  358.    out_in_tagged_out_memory is
  359.       -- Append terse printable represention of current object
  360.       -- in `tagged_out_memory';
  361.       do
  362.      tagged_out_memory.append(generating_type);
  363.      if not is_expanded_type then
  364.         tagged_out_memory.extend('#');
  365.         Current.to_pointer.append_in(tagged_out_memory);
  366.      end;
  367.      tagged_out_memory.extend('[');
  368.      fill_tagged_out_memory;
  369.      tagged_out_memory.extend(']');
  370.       end;
  371.    
  372.    frozen tagged_out_memory: STRING is
  373.       once
  374.      !!Result.make(1024);
  375.       end;
  376.    
  377.    fill_tagged_out_memory is
  378.      -- Note : can be redefine to change printing of stack
  379.      --        when system crash.
  380.       do
  381.       end;
  382.    
  383. feature -- Basic named file handling :
  384.  
  385.    frozen file_tools: FILE_TOOLS is
  386.       once
  387.       end;
  388.    
  389.    file_exists(path: STRING): BOOLEAN is
  390.      -- True if `path' is an existing readable file.
  391.       require
  392.      path /= Void;
  393.       do
  394.      Result := file_tools.is_readable(path);
  395.       end;
  396.    
  397.    remove_file(path: STRING) is
  398.       require
  399.      path /= Void;
  400.       local
  401.      p: POINTER;
  402.       do
  403.      p := path.to_external;
  404.      c_inline_c("remove(((char*)_p));");
  405.       end;
  406.    
  407.    rename_file(old_path, new_path: STRING) is
  408.       require
  409.      old_path /= Void;
  410.      new_path /= Void;
  411.       local
  412.      op, np: POINTER;
  413.       do
  414.      op := old_path.to_external;
  415.      np := new_path.to_external;
  416.      c_inline_c("rename(((char*)_op),((char*)_np));");
  417.       end;
  418.  
  419.    same_files(path1, path2: STRING): BOOLEAN is
  420.      -- True if `path1' file exists and as the 
  421.      -- same contents as file `path2'.
  422.       require
  423.      path1 /= Void;
  424.      path2 /= Void;
  425.       do
  426.      Result := file_tools.same_files(path1,path2);
  427.       end;
  428.  
  429. feature -- Access to command-line arguments :
  430.    
  431.    argument_count: INTEGER is
  432.      -- Number of arguments given to command that started
  433.      -- system execution (command name does not count).
  434.       do
  435.      Result := command_arguments.upper;
  436.       ensure
  437.      Result >= 0;
  438.       end;
  439.    
  440.    argument(i: INTEGER): STRING is
  441.      -- `i' th argument of command that started system execution 
  442.      -- Gives the command name if `i' is 0.
  443.       require
  444.      i >= 0;
  445.      i <= argument_count;
  446.       do
  447.      Result := command_arguments.item(i);
  448.       ensure
  449.      Result /= Void
  450.       end;
  451.  
  452.    frozen command_arguments: FIXED_ARRAY[STRING] is
  453.      -- Give an acces to arguments command line including the
  454.      -- command name at index 0.
  455.       local
  456.      i: INTEGER;
  457.      arg: STRING;
  458.       once
  459.      from
  460.         c_inline_c("_i=se_argc;");
  461.         !!Result.make(i);
  462.      until
  463.         i = 0
  464.      loop
  465.         c_inline_c("_arg=((T0*)e2s(se_argv[--_i]));");
  466.         Result.put(arg,i);
  467.      end;
  468.       ensure
  469.      not Result.empty
  470.       end;
  471.    
  472.    get_environment_variable(name: STRING): STRING is
  473.      -- To get the value of a system environment variable
  474.      -- (like "PATH" on Unix for example).
  475.      -- Gives Void when system variable `name' is undefined.
  476.       require
  477.      name /= Void
  478.       local
  479.      p: POINTER;
  480.       do
  481.      p := name.to_external;
  482.      c_inline_c("_p=((void*)getenv((char*)_p));");
  483.      if p.is_not_void then
  484.         c_inline_c("R=(T0*)e2s((char*)_p);");
  485.      end;
  486.       ensure
  487.      Result /= Void implies not Result.empty
  488.       end;
  489.    
  490. feature -- System calls and crashing :
  491.    
  492.    frozen crash is
  493.      -- Print Run Time Stack (unless "-boost" mode) 
  494.      -- and then exit with `exit_failure_code'.
  495.      -- See also `print'.
  496.       do
  497.      c_inline_c("rsp();");
  498.      die_with_code(exit_failure_code);
  499.       end;
  500.    
  501.    frozen trace_switch(flag: BOOLEAN) is
  502.      -- May be used in combination with option "-trace" of
  503.      -- command `compile_to_c' (see compile_to_c.hlp for
  504.      -- details).
  505.       external "CSE"
  506.       end;
  507.  
  508.    system(cmd: STRING) is
  509.      -- To execute a `cmd' at system level.
  510.      -- For example, "ls -l" on UNIX.
  511.       local
  512.      p: POINTER;
  513.       do
  514.      p := cmd.to_external;
  515.      c_inline_c("system(((char*)_p));");
  516.       end;
  517.    
  518.    frozen die_with_code(code:INTEGER) is
  519.      -- Terminate execution with exit status code `code'.
  520.      -- Do not print any message.
  521.       require
  522.      code = exit_success_code or else
  523.      code = exit_failure_code;
  524.       do
  525.      c_inline_c("exit(a1);");
  526.       end;
  527.    
  528.    exit_success_code: INTEGER is 0;
  529.    
  530.    exit_failure_code: INTEGER is 1;
  531.    
  532. feature -- Maths constants :
  533.  
  534.    Pi: DOUBLE is 3.1415926535897932384626; 
  535.      
  536.    Evalue: DOUBLE is  2.71828182845904523536;
  537.    
  538.    Deg: DOUBLE is 57.295780; -- Deg/Radian.
  539.    
  540.    Phi: DOUBLE is 1.618034; -- Golden Ratio.
  541.    
  542. feature -- Character names :
  543.  
  544.    Ctrl_a: CHARACTER is '%/1/';
  545.    Ctrl_b: CHARACTER is '%/2/';
  546.    Ctrl_c: CHARACTER is '%/3/';
  547.    Ctrl_d: CHARACTER is '%/4/';
  548.    Ctrl_e: CHARACTER is '%/5/';
  549.    Ctrl_f: CHARACTER is '%/6/';
  550.    Ctrl_g: CHARACTER is '%/7/';
  551.    Ch_del: CHARACTER is '%/8/';
  552.    Ch_tab: CHARACTER is '%/9/';
  553.    Ctrl_j: CHARACTER is '%/10/';
  554.    Ctrl_k: CHARACTER is '%/11/';
  555.    Ctrl_l: CHARACTER is '%/12/';
  556.    Ctrl_m: CHARACTER is '%/13/';
  557.    Ctrl_n: CHARACTER is '%/14/';
  558.    Ctrl_o: CHARACTER is '%/15/';
  559.    Ctrl_p: CHARACTER is '%/16/';
  560.    Ctrl_q: CHARACTER is '%/17/';
  561.    Ctrl_r: CHARACTER is '%/18/';
  562.    Ctrl_s: CHARACTER is '%/19/';
  563.    Ctrl_t: CHARACTER is '%/20/';
  564.    Ctrl_u: CHARACTER is '%/21/';
  565.    Ctrl_v: CHARACTER is '%/22/';
  566.    Ctrl_w: CHARACTER is '%/23/';
  567.    Ctrl_x: CHARACTER is '%/24/';
  568.    Ctrl_y: CHARACTER is '%/25/';
  569.    Ctrl_z: CHARACTER is '%/26/';
  570.  
  571. feature -- Hashing :
  572.    
  573.    hash_code: INTEGER is
  574.       external "CSE"
  575.       ensure
  576.      non_negative: Result >= 0
  577.       end;
  578.    
  579. feature -- Should not exist :
  580.    
  581.    not_yet_implemented is
  582.       do
  583.      std_error.put_string(
  584.       "Sorry, Some Feature is Not Yet Implemented.%N%
  585.        %Please, if you can write it by yourself and if you send me%N%
  586.        %the corresponding tested Eiffel code, I may put it in the%N% 
  587.        %standard library!%N%
  588.        %Many Thanks in advance.%N%  
  589.        %D.Colnet e-mail: colnet@loria.fr%N");
  590.      crash;
  591.        end;
  592.        
  593. feature -- The Guru section :
  594.    
  595.    to_pointer: POINTER is
  596.       -- Explicit conversion of a reference into POINTER type.
  597.       require
  598.      not is_expanded_type
  599.       external "CSE"
  600.       end;
  601.  
  602.    frozen is_expanded_type: BOOLEAN is
  603.      -- Target is not evaluated (Statically computed).
  604.      -- Result is true if target static type is an expanded type.
  605.      -- Usefull for formal generic type.
  606.       external "CSE"
  607.       end;
  608.    
  609.    frozen is_basic_expanded_type: BOOLEAN is
  610.      -- Target is not evaluated (Statically computed).
  611.      -- Result is true if target static type is one of the 
  612.      -- following types : BOOLEAN, CHARACTER, INTEGER, REAL,
  613.      -- DOUBLE or POINTER.
  614.       external "CSE"
  615.       ensure
  616.      Result implies is_expanded_type
  617.       end;
  618.    
  619.    frozen object_size: INTEGER is
  620.      -- Gives the size of the current object at first level 
  621.      -- only (pointed sub-object are not concerned).  
  622.      -- The result is given in number of CHARACTER.
  623.       external "CSE"
  624.       end;
  625.  
  626. feature {NONE} -- The Guru section :
  627.    
  628.    c_inline_h(c_code: STRING) is
  629.      -- Target must be Current and `c_code' must be a manifest
  630.      -- string. Write `c_code' in the heading C file.
  631.       external "CSE"
  632.       end;
  633.  
  634.    c_inline_c(c_code: STRING) is
  635.      -- Target must be Current and `c_code' must be a manifest
  636.      -- string. Write `c_code' in the stream at current position.
  637.       external "CSE"
  638.       end;
  639.  
  640.    object_id_memory: ARRAY[ANY] is
  641.       -- For a portable implementation of `id_object'/`object_id'.
  642.       -- Note: I think that the pair `id_object'/`object_id' is
  643.       -- a stupid one. It should be removed.
  644.       once
  645.      !!Result.with_capacity(256,1);
  646.       end;
  647.  
  648. feature {NONE} -- For the guru himself :
  649.  
  650.    frozen se_guru01 is
  651.      -- Implementation of `twin' : inline some code to produce 
  652.      -- the good basic memory allocation and then to call the
  653.      -- default `copy' or a customized one if any.
  654.       require
  655.      not is_expanded_type
  656.       external "CSE"
  657.       end;
  658.  
  659.    frozen se_guru02 is
  660.      -- Implementation of `standard_is_equal' : inline some code
  661.      -- to compare field by bield the two objects.
  662.       require
  663.      not is_expanded_type
  664.       external "CSE"
  665.       end;
  666.  
  667.    frozen se_guru03 is
  668.      -- Implementation of `copy' : inline some code
  669.      -- implement the default behavior of `copy'.
  670.       require
  671.      not is_expanded_type
  672.       external "CSE"
  673.       end;
  674.  
  675. end -- GENERAL
  676.